package com.mccken.eshop.order.service.impl;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.mccken.eshop.common.utils.ParamCheckUtil;
import com.mccken.eshop.market.domain.dto.CalculateOrderAmountDTO;
import com.mccken.eshop.order.domain.request.CreateOrderParams;
import com.mccken.eshop.order.domain.request.GenOrderIdParams;
import com.mccken.eshop.order.domain.response.CreateOrderResult;
import com.mccken.eshop.order.domain.response.GenOrderIdResult;
import com.mccken.eshop.order.enums.OrderNoTypeEnum;
import com.mccken.eshop.order.manager.OrderNoManager;
import com.mccken.eshop.order.service.OrderService;
import com.mccken.eshop.product.domain.dto.ProductSkuDTO;

import cn.hutool.core.math.Calculator;
import lombok.extern.slf4j.Slf4j;

/**
 * @program: mccken-collect
 * @description:
 * @author: mccken
 * @create: 2022-08-28 16:23
 **/
@Service
@Slf4j
public class OrderServiceImpl implements OrderService {

	@Autowired
	private OrderNoManager orderNoManager; 
	
	/**
	 * 生成订单号接口
	 * 
	 * @param params
	 * @return
	 */
	@Override
	public GenOrderIdResult genOrderId(GenOrderIdParams params) {
		
		// 参数检查
		String userId = params.getUserId();
		Integer businessIdentifier = params.getBusinessIdentifier();
		ParamCheckUtil.checkStringNonEmpty(userId);
		ParamCheckUtil.checkObjectNonNull(businessIdentifier);

		String orderId = orderNoManager.genOrderId(OrderNoTypeEnum.SALE_ORDER.getCode(), userId);
		GenOrderIdResult genOrderIdResult = new GenOrderIdResult();
		genOrderIdResult.setOrderId(orderId);
		return genOrderIdResult;
	}

	@Override
	public CreateOrderResult createOrder(CreateOrderParams params) {
		// 1. 入参检查
		this.checkCreateOrderRequestParam(params);

		// 2. 风控检查
		this.checkRisk(params);

		//3. 获取商品信息
		List<ProductSkuDTO> productSkuDTOList = this.listProductSkus(params);

		// 4. 计算订单价格
		CalculateOrderAmountDTO calculateOrderAmountDTO =  this.calculateOrderAmount(params, productSkuDTOList);
		
		// 5. 验证订单实付金额
		this.checkRealPayAmount(params, calculateOrderAmountDTO);
		
		// 6. 锁定优惠券
		this.lockUserCoupon(params);
		
		// 7. 锁定商品库存
		this.lockProductStock(params);
				
		// 8. 生成订单到数据库
		this.addNewOrder(params, productSkuDTOList, calculateOrderAmountDTO);
		
		// 9. 发送订单延迟消息用于支付超时时自动取消订单
		this.sendPayOrderTimeoutDelayMessage(params);
		
		// 返回订单信息
		CreateOrderResult result = new CreateOrderResult();
		result.setOrderId(params.getOrderId());
		return result;
	}
}
